﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;

namespace IBoLT.SettingWindows
{
	/// <summary>
	/// Логика взаимодействия для Mosaic.xaml
	/// </summary>
	public partial class Mosaic : Window
	{
		// Размер мозаик
		public int mSize;
		public int mWidth;
		public int mHeight;

		// Тип мозаик
		public int mType;

		// Размер текстуры предпросмотра
		private int tWidth;
		private int tHeight;

		// Тектура для предпросмотра
		System.Drawing.Bitmap texture;

		public Mosaic(System.Drawing.Bitmap sourcePreview)
		{
			texture = sourcePreview;

			InitializeComponent();
			// Добавляю обработчик к событиям в коде, т.к. для его работы необходимо создание формы
			sliderMSize.ValueChanged += hMosaicPreview;
			sliderMWidth.ValueChanged += hMosaicPreview;
			sliderMHeight.ValueChanged += hMosaicPreview;

			typeMosaic.SelectionChanged += typeMosaic_SelectionChanged;

			// Привязка команд к обработчикам //
			CommandBinding commBind = new CommandBinding(CommandsIBoLT.cMosaicFilter, hMosaicFilterEx); this.CommandBindings.Add(commBind);
			
			wPreview.Width = tWidth = texture.Width;
			wPreview.Height = tHeight = texture.Height;

			typeMosaic_SelectionChanged(null, null);
		}

		// Обработчик выбора типа мозаик
		private void typeMosaic_SelectionChanged(object sender, SelectionChangedEventArgs e)
		{
			if (typeMosaic.SelectedIndex == 0 || typeMosaic.SelectedIndex == 2)
			{
				SquareAndRhomb.Visibility = Visibility.Visible;
				Rectangle.Visibility = Visibility.Hidden;
			}
			else if (typeMosaic.SelectedIndex == 1)
			{
				SquareAndRhomb.Visibility = Visibility.Hidden;
				Rectangle.Visibility = Visibility.Visible;
			}

			hMosaicPreview(null, null);
		}

		// Обработчик изменения значений ползунков (предпросмотр)
		private void hMosaicPreview(object sender, RoutedPropertyChangedEventArgs<double> e)
		{
			if (typeMosaic.SelectedIndex == 0)
			{
				AForge.Imaging.Filters.Pixellate filter = new AForge.Imaging.Filters.Pixellate(Convert.ToInt32(sliderMSize.Value));
				wPreview.Source = SystemDrawingHelper.BitmapToBitmapImage(filter.Apply(texture));
			}
			else if (typeMosaic.SelectedIndex == 1)
			{
				AForge.Imaging.Filters.Pixellate filter = new AForge.Imaging.Filters.Pixellate(
					Convert.ToInt32(sliderMWidth.Value), Convert.ToInt32(sliderMHeight.Value));
				wPreview.Source = SystemDrawingHelper.BitmapToBitmapImage(filter.Apply(texture));
			}
			else if (typeMosaic.SelectedIndex == 2)
			{
				AForge.IntPoint[,] warpMap = new AForge.IntPoint[tHeight, tWidth];

				mSize = Convert.ToInt32(sliderMSize.Value);
				int maxOffset = -mSize + 1;

				for (int y = 0; y < tHeight; ++y)
				{
					for (int x = 0; x < tWidth; ++x)
					{
						int dx = (x / mSize) * mSize - x;
						int dy = (y / mSize) * mSize - y;

						if (dx + dy <= maxOffset)
						{
							dx = (x / mSize + 1) * mSize - 1 - x;
						}

						warpMap[y, x] = new AForge.IntPoint(dx, dy);
					}
				}
				AForge.Imaging.Filters.ImageWarp filter = new AForge.Imaging.Filters.ImageWarp(warpMap);
				wPreview.Source = SystemDrawingHelper.BitmapToBitmapImage(filter.Apply(texture));
			}
		}

		// Обработчик кнопки "Применить"
		private void hMosaicFilterEx(object sender, ExecutedRoutedEventArgs e)
		{
			mType = typeMosaic.SelectedIndex;
			mSize = Convert.ToInt32(sliderMSize.Value);
			mHeight = Convert.ToInt32(sliderMHeight.Value);
			mWidth = Convert.ToInt32(sliderMWidth.Value);			

			// Диалог успешен
			DialogResult = true;
		}
	}
}
